package com.kll.tv.utils

import android.util.Log
import java.io.BufferedReader
import java.io.IOException
import java.io.InputStream
import java.io.InputStreamReader
import java.util.concurrent.ExecutorService
import java.util.concurrent.Executors


/**
 * ====================================================
 * Created by Ziliang Cai on 2022/1/3 8:00 下午
 * <a href="mailto:752577456@qq.com">Contact me</a>
 * ====================================================
 */
class ProcessUtils {

    interface ProcessListener {
        fun finish()
    }

    companion object {
        /**
         * 读取RunTime.exec运行子进程的输入流 和 异常流
         *
         * @param inputStreams 输入流
         */
        private fun readStreamInfo(vararg inputStreams: InputStream) {
            val executorService: ExecutorService = Executors.newFixedThreadPool(inputStreams.size)
            for (`in` in inputStreams) {
                executorService.execute(CacheConsumer(`in`))
            }
            executorService.shutdown()
        }

        /**
         * Process缓存消费者
         */
        private class CacheConsumer internal constructor(`in`: InputStream) : Runnable {
            private val `in`: InputStream
            override fun run() {
                try {
                    val br = BufferedReader(InputStreamReader(`in`, "GBK"))
                    val result = StringBuilder()
                    var line: String?
                    while (br.readLine().also { line = it } != null) {
                        result.append(line).append("\n")
                    }
                    if (result.length > 0) {
                        Log.i("ProcessCacheConsumer", "==> $result")
                    }
                } catch (e: IOException) {
                    e.printStackTrace()
                } finally {
                    try {
                        `in`.close()
                    } catch (e: IOException) {
                        e.printStackTrace()
                    }
                }
            }

            init {
                this.`in` = `in`
            }
        }

        /**
         * 执行Process命令 cmd
         *
         * @param command         指令
         * @param o
         * @param timeout         超时时间
         * @param processListener 回调
         * @desc 注意：回调没有切换线程
         */
        fun executeProcess(
            command: ArrayList<String>,
            o: Any?,
            timeout: Long,
            processListener: ProcessListener
        ) {
            Thread {
                for (cmd in command) {
                    exec(cmd, timeout)
                }
                processListener.finish()
            }.start()
        }

        private fun exec(command: String, timeout: Long) {
            var process: Process? = null
            var worker: Worker? = null
            try {
                process = Runtime.getRuntime().exec(command)
                worker = Worker(process)
                worker.start()
                worker.join(timeout)
            } catch (ex: InterruptedException) {
                worker?.interrupt()
                Thread.currentThread().interrupt()
                ex.printStackTrace()
            } catch (ex: IOException) {
                worker?.interrupt()
                Thread.currentThread().interrupt()
                ex.printStackTrace()
            } finally {
                process?.destroy()
            }
        }
    }

    private class Worker(var process: Process): Thread() {

        override fun run() {
            var errorStream: InputStream? = null
            var inputStream: InputStream? = null
            try {
                errorStream = process!!.errorStream
                inputStream = process.inputStream
                readStreamInfo(errorStream, inputStream)
                process.waitFor()
                process.destroy()
            } catch (ignore: InterruptedException) {
            }
        }
    }


}